﻿using System.Collections.ObjectModel;
using Catel.Data;
using Catel.MVVM;

namespace Catel.Articles._03___MVVM.Examples.NestedUserControls
{
    /// <summary>
    /// Room view model.
    /// </summary>
    public class RoomViewModel : ViewModelBase
    {
        #region Variables
        private int _bedIndex = 1;
        private int _tableIndex = 1;
        #endregion

        #region Constructor & destructor
        /// <summary>
        /// Initializes a new instance of the <see cref="RoomViewModel"/> class.
        /// </summary>
        public RoomViewModel(Models.Room room)
        {
            // Store values
            Room = room;

            // Create commands
            AddTable = new Command<object>(AddTable_Execute);
            AddBed = new Command<object>(AddBed_Execute);
        }
        #endregion

        #region Properties
        /// <summary>
        /// Gets the title of the view model.
        /// </summary>
        /// <value>The title.</value>
        public override string Title { get { return "Room"; } }

        #region Models
        /// <summary>
        /// Gets or sets the room.
        /// </summary>
        [Model]
        public Models.Room Room
        {
            get { return GetValue<Models.Room>(RoomProperty); }
            private set { SetValue(RoomProperty, value); }
        }

        /// <summary>
        /// Register the Room property so it is known in the class.
        /// </summary>
        public static readonly PropertyData RoomProperty = RegisterProperty("Room", typeof(Models.Room));
        #endregion

        #region View model
        /// <summary>
        /// Gets or sets the name.
        /// </summary>
        [ViewModelToModel("Room")]
        public string Name
        {
            get { return GetValue<string>(NameProperty); }
            set { SetValue(NameProperty, value); }
        }

        /// <summary>
        /// Register the Name property so it is known in the class.
        /// </summary>
        public static readonly PropertyData NameProperty = RegisterProperty("Name", typeof(string));

        /// <summary>
        /// Gets or sets the table collection.
        /// </summary>
        [ViewModelToModel("Room")]
        public ObservableCollection<Models.Table> Tables
        {
            get { return GetValue<ObservableCollection<Models.Table>>(TablesProperty); }
            set { SetValue(TablesProperty, value); }
        }

        /// <summary>
        /// Register the Tables property so it is known in the class.
        /// </summary>
        public static readonly PropertyData TablesProperty = RegisterProperty("Tables", typeof(ObservableCollection<Models.Table>));

        /// <summary>
        /// Gets or sets the bed collection.
        /// </summary>
        [ViewModelToModel("Room")]
        public ObservableCollection<Models.Bed> Beds
        {
            get { return GetValue<ObservableCollection<Models.Bed>>(BedsProperty); }
            set { SetValue(BedsProperty, value); }
        }

        /// <summary>
        /// Register the Beds property so it is known in the class.
        /// </summary>
        public static readonly PropertyData BedsProperty = RegisterProperty("Beds", typeof(ObservableCollection<Models.Bed>));
        #endregion
        #endregion

        #region Commands
        /// <summary>
        /// Gets the AddTable command.
        /// </summary>
        public Command<object> AddTable { get; private set; }

        /// <summary>
        /// Method to invoke when the AddTable command is executed.
        /// </summary>
        /// <param name="parameter">The parameter of the command.</param>
        private void AddTable_Execute(object parameter)
        {
            Tables.Add(new Models.Table(string.Format("Table {0}", _tableIndex++)));
        }

        /// <summary>
        /// Gets the AddBed command.
        /// </summary>
        public Command<object> AddBed { get; private set; }

        /// <summary>
        /// Method to invoke when the AddBed command is executed.
        /// </summary>
        /// <param name="parameter">The parameter of the command.</param>
        private void AddBed_Execute(object parameter)
        {
            Beds.Add(new Models.Bed(string.Format("Bed {0}", _bedIndex++)));
        }
        #endregion
    }
}
